{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Imports"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [],
   "source": [
    "from matplotlib import pyplot as plt\n",
    "import seaborn as sns"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Draw background grid for each embedding plot"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {
    "collapsed": true,
    "jupyter": {
     "outputs_hidden": true
    }
   },
   "outputs": [],
   "source": [
    "def plot_grid():\n",
    "    fig, ax = plt.subplots(1, 1, tight_layout=True)\n",
    "\n",
    "    ax.get_xaxis().set_visible(False)\n",
    "    ax.get_yaxis().set_visible(False)\n",
    "    ax.spines['top'].set_visible(False)\n",
    "    ax.spines['right'].set_visible(False)\n",
    "    ax.spines['left'].set_visible(False)\n",
    "    ax.spines['bottom'].set_visible(False)\n",
    "\n",
    "    ax.set_facecolor(\"#F5F5F5\")\n",
    "    ax.set_aspect(\"equal\")\n",
    "    ax.set_xlim(0, 16)\n",
    "    ax.set_ylim(0, 16)\n",
    "\n",
    "    for x in range(16):\n",
    "        if x != 0:\n",
    "            ax.axvline(x, lw=0.5, color='#989898', zorder=5)\n",
    "        ax.axhline(x, lw=0.5, color='#989898', zorder=5)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Color palette"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "[(0.9677975592919913, 0.44127456009157356, 0.5358103155058701),\n (0.8087954113106306, 0.5634700050056693, 0.19502642696727285),\n (0.5920891529639701, 0.6418467016378244, 0.1935069134991043),\n (0.19783576093349015, 0.6955516966063037, 0.3995301037444499),\n (0.21044753832183283, 0.6773105080456748, 0.6433941168468681),\n (0.22335772267769388, 0.6565792317435265, 0.8171355503265633),\n (0.6423044349219739, 0.5497680051256467, 0.9582651433656727),\n (0.9603888539940703, 0.3814317878772117, 0.8683117650835491)]",
      "text/html": "<svg  width=\"440\" height=\"55\"><rect x=\"0\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#f77189;stroke-width:2;stroke:rgb(255,255,255)\"/><rect x=\"55\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#ce9032;stroke-width:2;stroke:rgb(255,255,255)\"/><rect x=\"110\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#97a431;stroke-width:2;stroke:rgb(255,255,255)\"/><rect x=\"165\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#32b166;stroke-width:2;stroke:rgb(255,255,255)\"/><rect x=\"220\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#36ada4;stroke-width:2;stroke:rgb(255,255,255)\"/><rect x=\"275\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#39a7d0;stroke-width:2;stroke:rgb(255,255,255)\"/><rect x=\"330\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#a48cf4;stroke-width:2;stroke:rgb(255,255,255)\"/><rect x=\"385\" y=\"0\" width=\"55\" height=\"55\" style=\"fill:#f561dd;stroke-width:2;stroke:rgb(255,255,255)\"/></svg>"
     },
     "execution_count": 7,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "# palette = sns.color_palette(as_cmap=True)\n",
    "palette = sns.color_palette(\"husl\", 8)\n",
    "cmap = lambda i : palette[i]\n",
    "palette"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Draw the bipartite template embedding pattern"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "iVBORw0KGgoAAAANSUhEUgAAARgAAAEYCAYAAACHjumMAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjMuMSwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/d3fzzAAAACXBIWXMAAAsTAAALEwEAmpwYAAAcrklEQVR4nO3debjN5doH8O9ae9tjhnolIiUHDUe7VCqlNKg0Dyp1NGk6pUnSnBSNcihKJCJHSGQI0ZEI4VCbzLYpMuQgw57s4f1jX++1rtz37+e5rfXUOu/1/fzT9bvXfu7f86ju9pq+RcrLy0FE5EP0z94AEf3/xQFDRN5wwBCRNxwwROQNBwwReZMa9mB+fn7cbzHl5eWhfv36f2oP7iFxPZJhD4nokQx7SESPZNgDAGRlZUW0uvffYPbu3fun9+AeEtcjGfaQiB7JsIdE9EiGPYThUyQi8oYDhoi84YAhIm84YIjIGw4YIvIm9G3qMNt37kXn0fOx9LdinJAZQYdaUVRLle9U7S3Yja0/bxf130rK0edXYGUh0DADePhIoKqyPrRHKdBvewSrioEGacAD1ctRNcV9/e5SYOCuVOQVR1A/rRztqpWgirI+rMeeMmDInjSs3R9FvUpluKNyMSorYztofUWPCIbnp2N9aQqOTSlFm6wiVI7KTwgE9dhbFsGookxsKE1F3ZQStE4vwGHK+rAe+8ojGFuSjY1lqagTLcG1qfuQHXHfw//1mFReBZtQCbWxH60iu0098hHF1GhVbEEaaqIYLct+QxbKTOcoQBTfpB6OrdF0HFVWhAtLdiJT6RF2joJIFLPSq+PXlDQcWVqMc4u2I7PcvUdhJIp52TWwPSUd1UuL0HTfNmQo68N6FEVSsLBKTeyslIHD9xeiye4tSC8vNZ2jKJqCxdWOxq60TFQrLkDjXb8gvcy9R3E0Bcur18Hu9CxUK9+PcxochazsDPVeQQ75N5jOo+dj/s5i7CsDFuwrR8/N+h9gkD6/Aj/kA/vKKv7a51f7HvptjyC3MIL8soq/9tuuD6ggA3elYnFRFPnlESwuimLgLvu8HbInDUuLU1BQHsHS4hQM2ZNm7jE8Px3LS1JRUB7B8pJUDM9PN60fVZSJlaWVUIgIVpZWwqiiTPMexpZkY3VZGgoRxeqyNIwtyTb3mFReBWuQjiJEsQbpmFRexbR+arQq1kcyUBSJYn0kA1OjVc17+Cb1cPyckoniSBQ/p2Tim9TDzT1mpVfHptRMFEdSsCk1E7PSq5vWz8uugc2VsrA/moLNlbIwL7uGeQ8Lq9TEtvRs7I+mYFt6NhZWqWnusbja0diecRhKoinYnnEYFlc72rR+efU62JFZuWJ9SgbmrNpq3sMhD5gfdxX/7nqR8TN5PxWEX7tYWhh+fTDLiiKh1y5WFkdDr12sLkkJvT6YNaWpodcu1pZVCr12sR5podcHsxHpodcufolmhF672JySEXp9MFtTM0KvXWxPywy9drEjPSv0+mB2Zvz+PzI7ovb/eB7ygNlfHn7tez0A7Eck9PpgSg74+QOv/1t6JGIPpQesOfD6j+hRGomEXv9RPcoOWHPg9cHXR0Ov/1t6lCdgD3yRl4i8OeQXeTVHXXWxqG3JzcVROTnyh9/52ml9aI/3volvD/1nxr+HQbPj2wMADJ0bX4/h/3ZaH9rj8x/i2wMAjFscX49JS53Wh/aYuiK+PQDA9NXx9Zi11ml9aI95P8e3BwBY+Et8PRbbX3M5EH+DISJvOGCIyBsOGCLyhgOGiLwJfZE3Ly8vMCvirGxZz83NFbUtW7ao60/P3OO0PqxHTvpvce3h5NSdce+hUXRHXHsAgPrl8lOUlh7HlcpPKVrPUadYvqBnPUfNQq2H/ABmUI/q+7Rz7Fd/NqhHtT3an6X8gFTYOQ77Tft7us+5R8YO7Z+r3erPBvVI3a79sy33FXaOyDbt3zH5ZxzUo2Sr8u94mf6z55xzjloPHTBhKVdzp8ob9Ql4NTtHqS+YLg/aK+jV8IAeud/JP3Dt54Lqz8+Vf9OD1gc91nWh/AfPsgcA6L5Y/gtg6fHuMvkvofUc/VfLQWA9x5D18l2knJzGzj1G/iLfRcrJOUldH9Rj7Db5LlJOTiPn9QDw1U75LlJOzl+ce3y7V76LlJNTT10f1GNukXwXKSfnGOf1APBjqXwXKSdH/zSv1mO58i5STuOj1PVB+BSJiLzhgCEibzhgiMgbDhgi8iahXxXYNOpLUdu9Px+bVm1Uflp+U1ZbH95DfjvUtgcZJ2Dfg4wDsO0BAGQcgK2HfOHNfI6IfPHPfI60uvH1yJYvhJrPUVW+GGs+R3X5orCpRy35wrT5HHVPiW8PAHD8afH1aHSG3teAv8EQkTccMETkDQcMEXnDAUNE3iT0Rd7ara8Ute25uajtmAejrQ/toeTBmPag5MGY96DkwZj2AKh5MKYeSh6M+RxKHoz5HEoejKmHkgdjPoeSB2M+h5IHY+qh5MGYz6HkwZjPoeTBmHowD4aIkhkHDBF5wwFDRN5wwBCRNxwwROQNA6fi3AMDp2IYOFWBgVMxDJxyXB/0GAOnYhg4VYGBUzF8ikRE3nDAEJE3HDBE5A0HDBF5k9DvIm34ZLSo/YZibFiUp/y0DHvS1of3kGFPtj0cmYA91IxzDwAitePrUUkGPZnPkSVfhDSfo2qD+HpUP8FpfWiPmifHtwcAOEaGPZl6KEFP5nM0OjO+PQDAyWfH1+PUc/W+BvwNhoi84YAhIm84YIjIGw4YIvImoS/y1r39BlHbmZuLuo6BU9r60B5K4JRpD0rglHkPSuCUaQ+AGjhl6qEETpnPoQROmc+hBE6ZeiiBU+ZzKIFT5nMogVOmHkrglPkcSuCU+RxK4JSlxxwGThFRMuOAISJvOGCIyBsOGCLyhnkwce6BeTAxzIOpwDyYGObBOK4Peox5MDHMg6nAPJgYPkUiIm84YIjIGw4YIvKGA4aIvOGAISJvIuXl5YEP5ufnBz545ttfidqIqv8RtQ2pZahbIufYnfk1RG1w1jb1XkE97i+uJWr90zY7r3+0XL4q/25Evnof1uOp1ONE7a2Sdc7rAaBzpny37pUCGQAU1OPVyg1F7fk9K9V7BfXoccSJotZxxzLn9QDw3lHyHaP2W+U7S0E9Pqpzqqjds/FH9V5BPYYed7qotV23wHk9AIxq0FTUWq+a59xjwknyLdurls5R7xXU4+uc5qJ2Sa787lzYOWae3kLUmi+Y7txj/tkXi9otAe8iZWVlRbQ6f4MhIm84YIjIGw4YIvKGA4aIvElo4NTx990mantyc3G8Y+CUtj60hxI4ZdqDEjhl3oMSOGXaA6AGTpl6KIFT5nMogVPmcyiBU6YeSuCU+RxK4JT5HErglKmHEjhlPocSOGU9x0wlcMrSYz4Dp4gomXHAEJE3HDBE5A0HDBF5w8CpOPfAwKkYBk5VYOBUDAOnHNcHPcbAqRgGTlVg4FQMnyIRkTccMETkDQcMEXnDAUNE3iQ0D+afaZtEbWNGFHUK5QuI95TXFbWPIhvUewX1eChFvnD2fql8gS1o/RMZDUTtH4WrTHt4rvIJovbanuXO6wHglSNOFrXOO5Y493izximi9vS2Req9gnq8U/s0UXtsk/z6QNg5+h13pqg9sG6+c4/BDc4WtTtXfa/eK6jH8BPPFbU2y2Y5rweAL045X9SuWzTDucfk0y8UtcsXyK+1hPWYfnZLUWvx/VTn9QAw57zLRe2c7yY79/jhwitFjXkwRJQ0OGCIyBsOGCLyhgOGiLxJaB5Mw0fbiVpBbi4aOubBaOtDeyh5MKY9KHkw5j0oeTCmPQBqHoyph5IHYz6HkgdjPoeSB2PqoeTBmM+h5MGYz6HkwVh6TFbyYKznmK7kwVjPMUfJg7H0+IF5MESUzDhgiMgbDhgi8oYDhoi84YAhIm8YOBXnHhg4FcPAqQoMnIph4JTj+qDHGDgVw8CpCgyciuFTJCLyhgOGiLzhgCEibzhgiMibhAZODSnLE7VNh6Wh9t5iUb8/vaGo9S9aqd4rqMcj2SeKWu99y5zXd6omX4Dsvku+UBnW48UjTxW1rr/+6LweAF49+nRRe/6XBc493q7bVNSe3DBPvVdQjz715bsAD+fNcV4PAANOaC5q9y6X3/cK6jG0cQtRa7t4unqvoB6fnXaxqN30w7+c1wPA+KaXitrV86Y495h6bitRazlrknqvoB4zW1wtas2nj3deDwDzLrlO1Jp+/YVzj0WtbhQ1Bk4RUdLggCEibzhgiMgbDhgi8iahgVMnPvWQqBXn5uJEx8ApbX1oDyVwyrQHJXDKvAclcMq0B0ANnDL1UAKnzOdQAqfM51ACp0w9lMAp8zmUwCnrOcYrgVOWHlOVwCnrOWYqgVPWc8xTAqcsPRYxcIqIkhkHDBF5wwFDRN5wwBCRN8yDiXMPzIOJYR5MBebBxDAPxnF90GPMg4lhHkwF5sHE8CkSEXnDAUNE3nDAEJE3HDBE5A0HDBF5k9DAqYH75LsAmw/PQq2d+aL+kBL29H5A2FNQjw7VTxW1ntt/dF7/bK0zRO31zfJ7PWE9Xq57lqi9tEF+tyhoPQC8Wb+ZqD2dJ7/jFNSjVyMZ9PT4Cvk9q7AeH/y1haj9/afpzusB4OPTLhG1u36Q3zkL6jG86WWi1mae/OcsrMeYZleI2vWzJzqvB4BJF8iwp1bfyrCnoB7fKEFPFypBT2E95rRqLWrnTBrlvB4AFl59i6g1GT/CucfSG24TNQZOEVHS4IAhIm84YIjIGw4YIvImoYFTjV/qIGplublo7Bg4pa0P7aEETpn2oAROmfegBE6Z9gCogVOmHkrglPkcSuCU+RxK4JSlx3AlcMp6jjFK4JT1HJOUwClLj2+UwCnrOeYogVPWcyxUAqcsPZYycIqIkhkHDBF5wwFDRN5wwBCRNwycinMPDJyKYeBUBQZOxTBwynF90GMMnIph4FQFBk7F8CkSEXnDAUNE3nDAEJE3HDBE5E1C82D6/2ehqG09sgqO+lW+mPpozTNF7d0t89V7BfXoVOdsUeu+8Xvn9S/WO0/Uuq79zrSHVxteIGrPr/zWeT0A9Dj5IlHruGSac48+OS1F7eHcqeq9gnoMOONyUbv335Od1wPA0HOuErW2cyY49xh1/rWi1nrGWPVeQT3GX3SDqF09bbTzegCYetlNotbyq8+ce8y8qo2oNZ8wXL1XUI/517cVtTPHDHVeDwCLbrpT1E75bLBzj5W3tRM15sEQUdLggCEibzhgiMgbDhgi8iaheTCnvf6sqOXm5uqfNFTyYLT1oT2UPBjTHpQ8GPMelDwY0x4ANQ/G1EPJgzGfQ8mDsZ5jqJIHY+kxSsmDsZ5jvJIHYz3HVCUPxtJjppIHYz3HfCUPxnqORUoejKXHSubBEFEy44AhIm84YIjIGw4YIvKGA4aIvGHgVJx7YOBUDAOnKjBwKoaBU47rgx5j4FQMA6cqMHAqhk+RiMgbDhgi8oYDhoi84YAhIm8SGjjVd6P8Xs6vtY7AkZvli7Ed6jUXtZ5r5XeDwno806CFqL2xarrz+i4nXSJrS+V3pMJ6vJFzmdxXrvyzCVoPAL3OuELUHv/3ROcefc++WtQe/H68eq+gHoOaXydqd8/8wnk9AHx6UWtRu3XaKOceYy67RdSu/2qEeq+gHhOvvE3UrvhymPN6AJh23e2idtEXnzj3mH3TXaLW7LOP1XsF9Vh4272i1mTYAOf1ALDkjgdE7eQh/Zx75N3zkKgxcIqIkgYHDBF5wwFDRN5wwBCRNwkNnDqj18uiZgmc0taH9lACp0x7UAKnzHtQAqdMewDUwClTDyVwynqOQUrglPUcnyqBU5YeY5TAKes5JiqBU9ZzTFMCpyw9ZiuBU9ZzLFQCp6znWKIETll65DFwioiSGQcMEXnDAUNE3nDAEJE3zIOJcw/Mg4lhHkwF5sHEMA/GcX3QY8yDiWEeTAXmwcTwKRIRecMBQ0TecMAQkTccMETkDQcMEXmT0MCp3qunidp/jqmB//l5m6h3OrGlqHVfNlW9V1CPFxpfLmrdFk92Xt+tyVWy58IJpj28fda1ovbk3LHO6wGgz3k3iNrD34127vFhi5tE7b7pn6n3CurxScs2onb71OHO6wHgsyvaitpNE4c69xh/7Z2idvXYweq9gnpMubGdqF36+UDn9QAwo819onb+8A+de8y7/e+i1vSTD9R7BfVY1O5hUTtlYB/n9QCw4v7HRK1R/3ece6xv/4SoMXCKiJIGBwwRecMBQ0TecMAQkTcJDZw6+4M3Rc0SOKWtD+2hBE6Z9qAETpn3oAROmfYAoI8SOGXp8aESOGU9xydK4JT1HJ8pgVOWHuOVwCnrOaYogVPWc8xQAqcsPeYpgVPWcyxSAqes51ihBE5Zeqxn4BQRJTMOGCLyhgOGiLzhgCEibxg4FeceGDgVw8CpCgycimHglOP6oMcYOBXDwKkKDJyK4VMkIvKGA4aIvOGAISJvOGCIyJuE5sH0XDxJ1HYeXwuHr9ks6s8qWSyvB2SxBPXo0lRmsXSZJ7NYgta/ce6NovbMrM9Ne+jV4mZRe3z6SOf1APBBy1tF7e9TP3XuMaiVzGG5e5LMYQnr8ek1Movl1nEyiyXsHGNuvEfUrv/8I+cek9rcL2qthvdX7xXUY1rbB0XtoqF9ndcDwOy7ZRZLs0EyiyWox0Ilh6WJksMS1mNp+46idtJ7PZzXA0DeY0+JWv133nLusenJZ0WNeTBElDQ4YIjIGw4YIvKGA4aIvEloHsx5g3uJmiUPRlsf2kPJgzHtQcmDse6hl5IHY9oDgA+UPBhLj0FKHoz1HJ8qeTDWc4xR8mAsPSYpeTDWc0xT8mCs55it5MFYeixU8mCs51iq5MFYz5Gn5MFYeoxgHgwRJTMOGCLyhgOGiLzhgCEibzhgiMgbBk7FuQcGTsUwcKoCA6diGDjluD7oMQZOxTBwqgIDp2L4FImIvOGAISJvOGCIyBsOGCLyJqGBU2/PHyNquxoeg2or5QtWLzRrLWrdZo9S7xXUo+v5t4jaizNGOK/vfvHfRK3Tv/5p2kPvy+8QtUcmD3FeDwAfXn23qN03fpBzjyHX3ytqd4wZoN4rqMfImx8QtZtH9nNeDwDj/tZe1K7553vOPabc9aioXfrxu+q9gnp8e28HUbtgQE/n9QAw98EnRe2svm8798h99GlRy3lX/39TB/VY0fF5UWvU41Xn9QCw7unOonbcm68499jywsuixsApIkoaHDBE5A0HDBF5wwFDRN4kNHDqghEfiJolcEpbH9ajqxI4ZdlDdyVwyrqH3krglOnPAcCHSuCUpccQJXDKeo6RSuCU9RzjlMApS48pSuCU9RzfKoFT1nPMVQKnLD1ylcAp6zlWKIFT1nOsUwKnLD0YOEVESY0Dhoi84YAhIm84YIjIG+bBxLkH5sHEMA+mAvNgYpgH47g+6DHmwcQwD6YC82Bi+BSJiLzhgCEibzhgiMgbDhgi8oYDhoi8SWjg1BszPhW13SfVQ5Wl8lX1Lhe3lbV/DVXvFdTj9cvuFLVnvxrsvL7nVfeIWocJH5n20Pf6+0XtwTH9ndcDwKCbHxS1u0f2de4x7LaHRe22YX3UewX1GH3nY6J2w+B3nNcDwMR7O4raFQN6OPeY9uBTonZR37fUewX1mPXIs6J2bu/XndcDwIInXhC10//RzbnHkqdfErWT35ThTWE98l7oKmr1u73ovB4ANnZ5TdTqdHnOucf2V2VIFgOniChpcMAQkTccMETkDQcMEXmT0MCpi8d9LGpBYTZdlMApbX1Yj9eVwCnLHnoqgVPWPfRVAqcsewCAQUrglKXHMCVwynqO0UrglPUcE5XAKUuPaUrglPUcs5TAKes5FiiBU5YeS5TAKes58pTAKes5BiuBU5YeDJwioqTGAUNE3nDAEJE3HDBE5A0Dp+LcAwOnYhg4VYGBUzEMnHJcH/QYA6diGDhVgYFTMXyKRETecMAQkTccMETkDQcMEXmT0DyYblMGidreUxrgsEWr5M9eea+ovfDlAPVeQT26X/uAqHUa2895fe/W7UXtkVHvmfbw4a2Pitp9n77rvB4APrmjg6jdPqSnc4+R7Z4UtZsHvq3eK6jHuAeeFrVr+sk8kLBzTHn4eVG7tM+rzj1mdOgsauf3fEW9V1CPuZ1k7spZ3WU+S9g5cp+T2S85r8mMmKAeK16S+TONXpY5NWE91nfrLmrHvtDJeT0AbHnjH6JW85knnHvs6iHzgJgHQ0RJgwOGiLzhgCEibzhgiMibhObBXDZluKgFZU10U/JgtPVhPboreTCWPfRW8mCse/hQyYOx7AEAPlHyYCw9Rip5MNZzjFPyYKznmKLkwVh6zFDyYKznmKvkwVjPkavkwVh6rFDyYKzn6K/kwVjPoeXBWHowD4aIkhoHDBF5wwFDRN5wwBCRNxwwROQNA6fi3AMDp2IYOFWBgVMxDJxyXB/0GAOnYhg4VYGBUzF8ikRE3nDAEJE3HDBE5A0HDBF5k9DvIk1sfr2o5Z9+IjYt6CJ/WAl70taH9mgjw55Me7hdhu+Y99BOhgCZ9gAADzwTX4/2MujJfI7HZdiT+RydZDiUqcdzMpzKfI7Ob8S3BwDoKsOeTD2UoCfzOXrI0DLzOd6R4WmmHu9/oPc14G8wROQNBwwRecMBQ0TecMAQkTcJ/b8KzH/yMlELCrNprgROzXzsEvVeQT0uUQKnvm5/ofP6q5TAqQn3NzftobUSODXq7mbO6wGgrRI4NbTtWc497lECpz5qc4Z6r6Ae7ZXAqfduPM15PQB0VAKnelwjP8kb1ON5JXDq1Vb6J3mDeryiBE51bik/yRt2jreUwKmnWshP8gb1eFcJnHr0XP2TvJbAqfubyk/yWgOn7mwiP8lrCZzi/1WAiJIGBwwRecMBQ0TecMAQkTfMg4lzD8yDiWEeTAXmwcQwD8ZxfdBjzIOJYR5MBebBxPApEhF5wwFDRN5wwBCRNxwwRORNQvNgxp3ZStQKz2qM9XNl3gnadnRaH9rjrqfi28N9z8W/h4dejG8PAPBYl/h6dOzqtD60xzOvxbcHAHjxrfh6vNLDaX1oj9d6xbcHAOjeO74evd53Wh/a473+8e0BAPp9FF+PgR/rfQ34GwwReXPIAya1tOR31ykHXB/MgT9vXZ+IHiklJaHXLqIHrDnw+o/oES3ZH3r9R/WIHLDmwOuDrt+/P/T6v6bHgT9/CHtIih4J2MMhD5iGxb//DEm9rfJ9+zB1t2wIvXZRZ/P60OuDOfqXdaHXLmptWht67aLGxrWh1wdTfcPa0GsXR6xfE3rt4vC1eaHXB1Nl7erQaxeHrVkVeu0ia/XK0OuDyVy1IvTaRdrK5aHXLlKXLwu9Ppjost9/LiljyybzHg55wLzZ7hKcVLADGcWF+Msva3HNvCmm9a1mT0a9TWuQXlSIepvWoNXsyeY9tPxuEo7dmIf0okIcuzEPLb+bZFrf4tsJOGbDaqQVFeCYDavR4tsJ5j00mzYOtdevQlphAWqvX4Vm08aZezSd8gVqrluFSoUFqLluFZpO+cK0vsnk0aixZiUqFRagxpqVaDJ5tHkPf/1yFKrnrUBqYQGq563AX78cZe7RaNwIHLFqOVIL8nHEquVoNG6EaX39McNRdeUypBTko+rKZag/Zrh5D3VHDUPlFUuRUpCPyiuWou6oYeYetUYMRfayJYjm5yN72RLUGjHUtL76sCHIXPoTovn5yFz6E6oPG2LeQ9UhHyNtyWJE8vchbcliVB3ysblH9uCBSF28CJF9+5C6eBGyBw80rU/7aACii3KBffuQ8fM6XHhmQ/MeDjkPxlVYXsUf1YN7SFyPZNhDInokwx4S0SMZ9gAwD4aI/gQcMETkDQcMEXnDAUNE3nDAEJE3oe8iERHFg7/BEJE3HDBE5A0HDBF5wwFDRN5wwBCRNxwwROTN/wIAh4EizjL82gAAAABJRU5ErkJggg==\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "\n",
    "red_grad = sns.color_palette(\"blend:#DEA9B2,#A72A3E\", 16)\n",
    "blue_grad = sns.color_palette(\"blend:#2A81AE,#9EC8DE\", 16)\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=red_grad[i])\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=blue_grad[i])\n",
    "\n",
    "plt.savefig(\"diagrams/bp.png\", dpi=300)"
   ]
  },
  {
   "cell_type": "markdown",
   "source": [
    "Draw the bipartite template embedding pattern (with a fault)"
   ],
   "metadata": {
    "collapsed": false
   }
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "\n",
    "grey = \"#A9A9A9\"\n",
    "red_grad = sns.color_palette(\"blend:#DEA9B2,#A72A3E\", 16)\n",
    "blue_grad = sns.color_palette(\"blend:#2A81AE,#9EC8DE\", 16)\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=grey)\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=grey)\n",
    "\n",
    "plt.plot([10.5, 10.5],\n",
    "         [11.5, 15.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=\"#60A2C4\")\n",
    "\n",
    "plt.plot([10.5, 10.5],\n",
    "         [9.5, 0.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=\"#60A2C4\")\n",
    "\n",
    "plt.plot([0.5, 15.5],\n",
    "         [10.5, 10.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=\"#BF6473\")\n",
    "\n",
    "plt.savefig(\"diagrams/bp_fault.png\", dpi=300)"
   ],
   "metadata": {
    "collapsed": false,
    "pycharm": {
     "name": "#%%\n"
    }
   }
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Draw the quadripartite template embedding pattern"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 10,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "\n",
    "\n",
    "red_grad = sns.color_palette(\"blend:#DEA9B2,#A72A3E\", 8)\n",
    "blue_grad = sns.color_palette(\"blend:#2A81AE,#9EC8DE\", 16)\n",
    "yellow_grad = sns.color_palette(\"blend:#DEDDA9,#A5A72A\", 8)\n",
    "green_grad = sns.color_palette(\"blend:#54AE2A,#9EDE9F\", 16)\n",
    "\n",
    "\n",
    "\n",
    "for i in range(0, 8):\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=red_grad[i])\n",
    "\n",
    "for i in range(8, 16):\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=yellow_grad[i - 8])\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [8.5, 15.5],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=blue_grad[i])\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 7.5],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=green_grad[i])\n",
    "\n",
    "plt.savefig(\"diagrams/quad.png\", dpi=300)"
   ]
  },
  {
   "cell_type": "markdown",
   "source": [
    "Draw the quadripartite template embedding pattern (with a fault)"
   ],
   "metadata": {
    "collapsed": false
   }
  },
  {
   "cell_type": "code",
   "execution_count": 11,
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "\n",
    "grey = \"#A9A9A9\"\n",
    "\n",
    "for i in range(0, 8):\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=grey)\n",
    "\n",
    "for i in range(8, 16):\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=grey)\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [8.5, 15.5],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=grey)\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 7.5],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=grey)\n",
    "\n",
    "plt.plot([10.5, 10.5],\n",
    "         [8.5, 15.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=\"#60A2C4\")\n",
    "\n",
    "plt.plot([10.5, 10.5],\n",
    "         [7.5, 6.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=\"#7DCA6E\")\n",
    "\n",
    "plt.plot([10.5, 10.5],\n",
    "         [4.5, 0.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=\"#7DCA6E\")\n",
    "\n",
    "plt.plot([0.5, 15.5],\n",
    "         [5.5, 5.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=\"#BDBF66\")\n",
    "\n",
    "plt.savefig(\"diagrams/quad_fault.png\", dpi=300)"
   ],
   "metadata": {
    "collapsed": false,
    "pycharm": {
     "name": "#%%\n"
    }
   }
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Draw the clique overlap annealing embedding pattern"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "red_grad = sns.color_palette(\"blend:#DEA9B2,#A72A3E\", 16)\n",
    "blue_grad = sns.color_palette(\"blend:#2A81AE,#9EC8DE\", 16)\n",
    "for i in range(16):\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=red_grad[i])\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [15.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=red_grad[i])\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=blue_grad[i])\n",
    "\n",
    "plt.savefig(\"diagrams/coa_gp.png\", dpi=300)"
   ]
  },
  {
   "cell_type": "markdown",
   "source": [
    "Draw the pssa embedding pattern"
   ],
   "metadata": {
    "collapsed": false
   }
  },
  {
   "cell_type": "code",
   "execution_count": 13,
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "iVBORw0KGgoAAAANSUhEUgAAARgAAAEYCAYAAACHjumMAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjMuMSwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/d3fzzAAAACXBIWXMAAAsTAAALEwEAmpwYAAAcCUlEQVR4nO3de3BcZ3kG8GdXK+2uJOtiy9bFlnGcYGObRKEmCbkRmHAnhF6g0A60tBSGloHCtIUyTEOhQ5lQIE6AwgQolzAtEEohCQHfaFxit4kxsRxsx47vsnWXVpe979k9/UMTNvL3nqPznbOftJKe33/7Sd+772fHb+Rzzj4O2bYNIiITwgvdABEtXRwwRGQMBwwRGcMBQ0TGcMAQkTERty+m0+nAt5hOnz6NK6+8ckFrsIfK1aiGHipRoxp6qESNaugBAOrr60PSuvGfYJLJ5ILXYA+Vq1ENPVSiRjX0UIka1dCDG/4ViYiM4YAhImM4YIjIGA4YIjKGA4aIjHG9Te1mNJHEXT86iGOTebwoHsKHO8Noiah3qpKZKQz1jSrrtm2jVCjALpUQCocRrq1FKCTe6XKuUSrBSmVQKloI10QQaYgjFFZnpuP+Ygm5yUkU8wXU1NUi2tyMUI08c51qlIpFZIZHYeXyiETrEF/ThnBNjef9AFCyLKT6B2GlM4jUx9HQ1YFwRP2tceyhYGHqXB8KqTRqG+rRtKEb4Vr5t9apRjFfwMSpM8hPJVHX1IiWqzaipq5W6xzFfB7jR08gNzmNaPMKrNy2GTV1dd57yOUwcvgochMTiLa0YPW121ATjWqdw8rmMHTwMLJjCcRWtaL9umsRiak13M5hZbIYOHAQmdExxNtWofOm6xCJx7z3kMng4mMHkB4aRX17G9a94iZE4nGtcxTSGVzYvQ/pwSHUd7Rj/atvQ229WsPtHIVUGuce3YvUpUE0rO3AhjfcjtqGeu89pFI4/eOfI3mxH00bX4CX3v1xxDvWiO/lxPdPMHf96CAOJvJIlYBDKRv3DJS09j83XICZQVEqFLR7sFIZlCwLsGf+kFqpjNb+3OQkirk8YNso5vLITU5q95AZHoWVyQKlEqxMFplh+TfbTap/EIVkCnaphEIyhVT/oNb+qXN9yE9Nwy4WkZ+axtS5Pu0eJk6dQS4xCbtYRC4xiYlTZ7RrjB89gexYArZlITuWwPjRE1r7Rw4fRWZkFKWChczIKEYOH9XuYejgYaQHh1EqFJAeHMbQwcPaNQYOHESqfxClfAGp/kEMHDiotf/iYweQ7OtHKZ9Hsq8fFx87oN3Dhd37MH2+D8VcHtPn+3Bh9z7tGuce3YupM+dRzOUwdeY8zj26V2v/6R//HJOnzqKYzSFx7CR+9dFPa/fge8AcnsjPen1E85m854aL02svSpbl+nouxVze9bUXVjbr+tqLQirt+nou+emk62svchNTrq+9yCYmXF/PuX9s3PW1F5cPeD8DPz047Pp6Lpf/D0L3fxgAkLzY7/rai+nzF11fz2Xq7IVZrydOntbuwfeAKdjur5eNy8/t59fh8kwe3YyeoPsrVaNku7+eq4UK/E+nGmrYxZLra281iq6v56OGst/S74EXeYnIGN8XeSXtd9yurA329qK9p0dZv/TDn3ra71bjwgM/CtTDma/9e+AeJu/7t0A9AMD4MfVahU6N4UNHPO13q9G//8lAPQBA357/CVTj7CO7PO13q/Hsgw8H6gEAnnngwUA1fnP/A572u/Zx39cC9QAAuPtLwWp88nNyXQ38CYaIjOGAISJjOGCIyBgOGCIyxvUi7+nTpx2zIm5oUNd7e3uVtcFB+RmAqYL6rMeosN+txiTU51YSGj0kIurtw2nNHsZi6ozOaPQAACON6tOueY0aQ63q05klzXMMrW5S1nR+PwFgpHNloBpj3epTotJ+txqJjZ2BegCAiU3dgWpMbb3C0363GslrXhioBwBIb98SqEb2hqs97QeAG2+8UVx3HTBuKVdP7Fab+pLD1ewe6S7Ss+pDP2udroY71LhwRH3wZ71GD2eeVJ8U3ajZw8l9h5S1TRo9AMDxnfuVtS0aNZ7+8S+Utas1z1H63qOevs9tvfBN9a6eTo3MV9S7ek77nb42/YVvBuoBACb++SuBaoz+wz2e9zt9bfDvPhOoBwC4dOgf1e/d4b3G+Sf+Xv2+LzmfQ8K/IhGRMRwwRGQMBwwRGcMBQ0TGBPqoQG1NGOEQfpvjcuu9e5Tv2R6fxqHHRoTdz2V02FgRBu5alQeEjw8AM3ecpIvCEukjCEH3z3cPlajBc1Suh0rUWCrn0OX7J5jamjBqwiHHkCjvQpguhfCpMfVWLREtbr4HTDjoXLnMtP4n2omoyvkeMJpRHx5UeGIR0YLzfQ2mUCwBmH0Nhojo+QJd5C1cltR18G9fq3xPb28vdghPCUoXhNe+5Y3i+4z29opP+Up5MFINp/1SHoxuDyeFPBidHgBg6rP/GqjG+NGTnva71ZAyZXTPMfC4mimjU0PKk9E9x9mHdwfqAQBOCZkyOjWe+Y6aJ6N7DilTRvccvfd+PVCNQ0KejC7epiYiYzhgiMgYDhgiMoYDhoiM4YAhImMWLHBqe3za0363GgycmsHAqTIGTpUt68Ap6fNJ0u1stxoMnJrBwKkyBk6VMXCKiJY0DhgiMoYDhoiM4YAhImNCtu38seh0Ou34xes/txPxuggic2TC9EQn0ZtrDtTk3DVsNIZsfDQ+jbXCnaFzyGMD1Ds1VjarrEViMfEdnGpkExPKWqy1xfN+AEgNqBfMGzo7PNeYPHNeWWve+ALxvZxqjAn/PvaqrZs97weA4UPqHYY129WLgk41+vc/oax13XyD+F5ONS4In2da/6qXe94PyP9G9hV3vMZzjWcffEhZe+Fb7xTfy6nG8Qd+oKxteecfet4PyJ9nevF73+m5xmHh38e+8+DPxPeqr68Xh4Dvn2DidRHU1oSr5JPUISTtMO7OrFjoRojoeXwPmEilE6cqIGlXX09Ey5nvAWNVPnGqAjhgiKqJ7wGTyVsoFEtwu4ZDRMub78ApG0A6b81acwqckp4SlAKnfvnXrxLfy6nGq77838ra+nf+vrKW6O0Vn/CVAqek/W41pMApnR4A4LgQOKVT4+lPqk+O6p5j7GPqk6O655Au8urUkC7y6p5DvMireQ7pIq9ODekir+45pIu8uueQLvLq1JAu8uribWoiMoYDhoiM4YAhImM4YIjImEWdB9MTnQzUA/NgnleDeTC/xTyYGcs+D6b38XFP3+e0zjyYMubBlDEPZgbzYIioqnHAEJExHDBEZAwHDBEZwwFDRMb4D5z6/E40x6Koi7hnwmyLJHDUag3UZNAac++30YgSPoBhdIYs8TsuREpYb6nz2MoIoVVxNbTKaT8A5ITQqqgQWuVUI9U/pKw1dLWL7+VUw2tolds5xo+qoVUrt6mhVU41vAZWudXof/xJZa3rlus97weAPuHzTN1CaJVTjbMPC4FVb1IDq9xqeA2tcjvHM995UFl70Z+81XMN6bNM8xY41RyLIlpbUyWBU0GFkEQNvgj1OQwi8s/3gKmNLL2/XSX5N0aiivL9J6pgqU/BLn5L4acxourhe8BMZnPIFYoMnCIiR/4Dp2xgIpObtVYNgVN73v9Kz/vvuP+XytrG9/yx2MN0b6/4MQIpcEqq4bQfkAOndGpIgVO653hKCJzSPcf4hz4RqIZ0kVf3HNJFXt1zSBd5dWpIF3l1zyFd5NU9h3SRV6eGdJFXFy86EJExHDBEZAwHDBEZwwFDRMYs68CpbZFE4B4YOFXGwKkZDJwqW9aBUx9/YsrzfqevMXCqjIFTMxg4Vca/IhGRMRwwRGQMBwwRGcMBQ0TG+M6DueHzu9DWGENsjsiGzeFxnCipdxd0BK0xLz3YNurtIt6TuYD2Ul758sVYGOuy8gdEi1k1U6YmpmbKONXIJdS7adHWZvG9nGqkBoRMmU41U8btHFNCpkyTkCnjVGP8mJAns1XNk3GrMXzoiLK2Zvs1nvcDwMB+9eMGnTermTJONbzmybjVkP597CvuUDNl3M5x6sGHlbWr3vomzzWeeUD9qMG85cG0NcYQr4sskTyYCgiFkA5H8LX4+oXuhKhq+B4wdZGaSvaxZKRD/HUheo7vAZO3ipXsY+ngT3REv+V7wIwms8jkLebBEJEj33kwJdvG8HRm1tpSyIN55L23avXwlm8eUNY2ffDPlbVMb6/jE75SHoxODSkPRtrvVkPKg9E9x6+EPBidGv/3vo962u9WY/hPPxSoB0C+yKtTQ7rIq3sO6SKv7jmki7w6NaSLvLp4m5qIjOGAISJjOGCIyBgOGCIyhgOGiIxh4FTAHjaH1Uwa7aAmBk4BYODU8zFwioFTAIB/+nUqUA8AA6eew8CpMgZOERHNgQOGiIzhgCEiYzhgiMgY34FTL/vCLnQ016O+LoKwyyeIr7RHcTrUFqjJoDUWTQ+2jfqShXeMncRqSw2hutRYh7VJNczKuuzfCAeASDwqvoVTjawQWhUTQquc9gNAql8IrepSQ6ucakwKgVXNQmCVW42xoyeVtVXbNnneD3gPrXKqIf372F23qIFVbjUuCJ9nWi+EVrmd4+zDu5W1K970as81nhU+yzRvgVMdzfVojNa6DhfSFAohXVOL765S/0AQLUa+B0y8lsFKpqTDvj/kTlRVfA+YTIGBU8bwp0JaInwPmMHJNJK5AkoMnCIiB75/Fi+WbFxKzH6KlYFTM374Zzd53g8A7/juE8ralo/8lbKW7+0Vn/CVAqek/W41pMApnR4AOXBKp4YUOKV7jseFwCndcwy/7X2BakgXeXXPIV3k1T2HdJFXp4Z0kVcXb1MTkTEcMERkDAcMERnDAUNExjAPJmAPlciDudIeDVSDeTBlzIMpYx7MZZZrHsy/PK1+LECnBvNgypgHU8Y8GCJa0jhgiMgYDhgiMoYDhoiM4YAhImMCBU51tzaiMeaeCbOhOIJzNasDNRm0xrLpwbYRLxbwlr4jWJXPiN8y0FqPzkRaWbey6p2sSCzmeT8A5BITylq0tcVzjdSAemeyobNDfC+nGl5Dq9zOMX7shLK2cutmzzWGD6m3ctdsl+++ONXo369+Pq3r5hs87weAPuHzTN1CaJVTjbOP7FLW5i1wqru1EU3xOgZOVZNQCJlIHX7YraavES0E3wOmPspQpGqVqald6BaIAAQYMOmcVck+qJL4UyVVCd8Dpi+RxFQmz8ApInIUKHDq3NjszxMxcGpGJQKnvvsO9YKeU413f+9XytrVn/iw+F6l3l7xYwRS4JRUw2k/IAdO6dSQAqd0zyEFTumeY58QOKVTY++d7/K0361G/2veHqgHQL7Iq1NDusiri7epicgYDhgiMoYDhoiM4YAhImMYOBWwh2oInNpQVLN1dM/BwKkyBk7NYOAUA6cAAPcdL3je7/Q1Bk6VMXBqBgOniKiqccAQkTEcMERkDAcMERnjOw/mxi/swsbVTWiK1SEcdv5w3br8EC7WtQdqMmgN9qBRw7YRs/J444kn0ZpVL2APrW5C+4h6cRwAihn1YnVNXM2UcarhNU/GrUaqf0hZa+hSz+t2jikhU6ZJyJRxqjF+VMiT2abmybjV8Jop43aOAeHfyO685XrPNaSPGsxbHszG1U1oqY+6DhdahEIhZGuj+Olm9T9EIl2+B0xjlJkjS1k2UrfQLdAS4HvAJHPqsxe0hDBThirA94A5MzKFiXQOpRLzYIhI5jsPxirZODk0+1F95sHMqIY8mG+8/aXieznVeP9/PqWsveQzH/O8H5DzYHRqSHkw0n63GlIejO45pDwYnRpSHozuOXYKeTC65xi49fcC1ZAu8uribWoiMoYDhoiM4YAhImM4YIjIGA4YIjKGgVMBe1gqgVPr8uoj9gyc8leDgVNlDJzyuN/pa0slcOr+U6VAPQAMnHoOA6fK+FckIjKGA4aIjOGAISJjOGCIyBjfgVM33bMbmzta0BJ3z4TpyA5gMKZe2dcRtAZ7qFwNT/ttG9FCDrf/eh+a0+rdwpHOlVg9oF6gt7Lqxe5ITA2scquRTah3FmOtzZ73A0BqQAit6lRDq5xqTAqBVc1CYJVbjbFjamjVqq1qaJXbOYYPHVHW1my/xnON/v1qYNW8BU5t7mjByoYYA6dIFQohVxfD3t+5baE7oQXme8CsiDGQiNzlaqML3QItMN8DZjqbr2QftBQxtGrZ8z1gTgxOYDyVZeAUETnyHThVKJbwm0uzLwzJgVMl9PSojxzrBU7JNbwHTsn79QKn5BreA6fk/YBO4JRcQy9wSq4hBU59+Q9e4nk/APzNQ08ray/d8UmhhvfAKWm/Ww0pcEqnB0AOnNKpIQVO6Z5DCpzSPcejQuCUTo2Hrnu9WFcHb1MTkTEcMERkDAcMERnDAUNExjAPJmAPzIMp68hKNdQYCObBzF2DeTDMgwHAPJjn+8559S6S0x0n5sG4f415MEREc+CAISJjOGCIyBgOGCIyhgOGiIzxHTh18z27sW3tSqxsiKHGJROmLdWP0YauQE0GrcEeKldjXnqwbdTls7jx8Z1oSqqPIgAzt7RX9Q0r61Ymp6xF4mpshNN+AMgJoVVRIbTKqUaqXwis6lIDq9xqeA2tcjvH+NGTytrKbZs815ACq+YtcGrb2pVYvSLuOlyIfAmFkI/G8b+3qB+epcXF94BpqWeYEJmVr5PjMmnx8D1gJtLqj6JEFcXAqkXP94A5emkcI9MZFBk4RUQOfAdO5YslPHVh9mdo5MCpAnp6tirreoFTcg3vgVPyfr3AKbmG98ApeT+gEzgl19ALnJJreA+ccj6HFDj1+Tulz7PINT7+s2PK2su+erf4XjqBU1IN3cApnRpS4JTuOaTAKd1zSIFTOjUYOEVEVY0DhoiM4YAhImM4YIjIGAZOBeyBgVNlQQOn2lLSOdSsG7caDJwqY+DUZRg45a/GUgmc+kG/ehfJ6Y6VUw0GTpUxcIqIljQOGCIyhgOGiIzhgCEiY/znwezYjWu729DW6B7Z0DJ9ERMr1gVqMmgN9lC5GtXQg6cato3aXBYv2fUTNE6pdwsTGzvRemZA3FrMqhfda2LqJ7udauQSE8patLVFfC+nGqkB9SZKQ2eH5/0AMCVkyjQJmTJONcaPnVDW5i0P5truNrQ31TMPhqpTKIRCLI6nXvPmhe5kWfM9YFqZB0OLQCHKTJmF5HvAJJgHQ4sBM2UWlO8Bc7hvFENTaebBEJEj/3kwVglPnp0dFCznwWTR07NZWdfLg5FreM+Dkffr5cHINbznwcj7AZ08GLmGXh6MXMN7HozzObznwcg1pDyYT79efpLXqcandqsXJm/59g5hv14ejE4NKQ9G2u9WQ8qD0T2HlAejU4N5MERU1ThgiMgYDhgiMoYDhoiM4YAhImMYOBWwBwZOlVVD4FTLtPRrqT76z8CpuWswcIqBUwAYOPV8PxlWb1M73VZn4JR7DQZOEVFV44AhImM4YIjIGA4YIjLGd+DULTv24LorVmPNijhqws5zqnGyD8lm9aq8jqA12EPlalRDD5Wo4Wm/bSOSzWDLT76P+sSY8uWJTd1oOdmnrFsZ9aJ9JC7HRjjVyAqhVTEhtMppPwCk+tW7eg1d7Z5rTAqBVfMWOHXdFavR2dzgOlyIFrVQCFa8Hsff/LaF7mTR8j0dVjUwyIeWBysWX+gWFi3fA2Yspf4YSLQkMbTKN98D5uDZEQxMplAsqQ9oEREBAQKnclYRjz87+2leOXAqhZ6eq5R1vcApuYb3wCl5v17glFzDe+CUvB/QCZySa+gFTsk1vAdOOZ/De+CUXEMvcEquIQVO3fVq9Ulet3N89rFTytpt3/+qUMN74JS0362GFDil0wMgB07p1GDgFBFVNQ4YIjKGA4aIjOGAISJjmAcTsAfmwZQtlTyYxknp91SN5WAeTBnzYJgH4/o15sGU7Uyod5Gc7jgxD8Yd/4pERMZwwBCRMRwwRGQMBwwRGcMBQ0TG+A6cunXHHtx0VQc6mt0Dp2Lj55Fd+YJATQatwR4qV6MaeqhEjXnpwbZRk05jw398C7Ex9fY5MHNLu+nYWWXdygqhVTE1IsVpPwDkEupjHNHWZs81UgPqYwfzFjh101UdWNvKwCkiR6EQig0NOPdH71roThaM7+nQtoKBU0ReFOvrF7qFBeN7wIxOM3CKyJNlHFjle8AcODWISwkGThGRM9+BU1mriF88c2nWmhw4NYWeHvWzGXqBU3IN74FT8n69wCm5hvfAKXk/oBM4JdfQC5ySa3gPnHI+h/fAKbmGXuCUXMN74JTzOaTAqY+8Qv2ogFON+/arF0xvf+hb4nvpBE5JNXQDp3RqMHCKiKoaBwwRGcMBQ0TGcMAQkTEMnArYAwOnyhg4NSM2Lv13pWYPudVg4BQDpwAwcOr5GDg1Y19SvYvkdMfKqQYDp4iI5sABQ0TGcMAQkTEcMERkjP88mHv34LbNXehqaUDEJbIhMnoWVpvzBS4vgtZgD5WrUQ09VKJGNfTgqYZtI5xKof0bX0HdyLDy5eQ1L0TjkWfFrcVMTlmriUc915DyZOYtD+a2zV1Yv3KF63AhooBCIZQaGzH07r9c6E588T0d2lcs34wLovlWamhY6BZ88T1ghqbTleyDiNws0kwZ3wNm34l+XBifhsU8GCJy4D8PplDEzt/0zVqT82DG0dPTrazr5cHINbznwcj79fJg5Bre82Dk/YBOHoxcQy8PRq7hPQ/G+Rze82DkGnp5MHIN73kwzufwngcj15DyYD54s3wh16nG/U/2KWuv3fU9Yb9eHoxODebBEFFV44AhImM4YIjIGA4YIjKGA4aIjGHgVMAeGDhVxsCpGZUInIqMSv9tq30xcAoMnJprnYFTMxg4VfZETr1N7XRbnYFTRLQsccAQkTEcMERkDAcMERnjO3Dq5ffuwe1burGutQGRGuc5FRo+A3vNxmBNBqzBHipXoxp6qESNauihEjU87bdthJJJtHzxHkSG1Dt96e1bUH/ouLJuZdWbD/MWOHX7lm5saFvhOlyIqAqEQrBXrMDEBz4872/tezp0NDNwimgxsRsb5/09fQ+YwUkGThEtKgsQWuV7wOw93odzo9OwigycIiKZ78CpTKGIR46cm7UmB06NoKenS1nXC5ySa3gPnJL36wVOyTW8B07J+wGdwCm5hl7glFzDe+CU8zm8B07JNfQCp+Qa3gOnnM/hPXBKrqEXOCXXkAKn3nu9+iSv2zm+/et+Ze0Nv/wvoUav+IQvA6eIqKpxwBCRMRwwRGQMBwwRGcM8mIA9MA+mjHkwM6olDyY0LP0ZU3+NmQfjUIN5MDOYB1PGPJiyw0X1LpLTHSfmwRDRosMBQ0TGcMAQkTEcMERkjO88mNvu24vXvXg91q9sdI1ssAZOIdIpXyDzKmgN9lC5GtXQQyVqVEMPlagxLz0UCggfP4a6b3wdb/7FD8RvccqD8f1ZpNe9eD02rm7yu52IFovaWpSu6UH+3X+hvdX3X5G6WpgHQ7SclK7U/0nJ94DJ5OUHoIhoaYqNq8+uzcX3gPndre1IpDKwSsyDIVrSCgXE+s7hlddt0t7q+xpMR1Mc73vZhjm/r7c0iJ6r2/2+TUVqsIfK1aiGHipRoxp6qESN+ethna/avE1NRMZwwBCRMRwwRGQMBwwRGcMBQ0TGuH5UgIgoCP4EQ0TGcMAQkTEcMERkDAcMERnDAUNExnDAEJEx/w/3Z+NNXlpOeQAAAABJRU5ErkJggg==\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "red_grad = sns.color_palette(\"blend:#DEA9B2,#A72A3E\", 16)\n",
    "blue_grad = sns.color_palette(\"blend:#2A81AE,#9EC8DE\", 16)\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [15.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=red_grad[i])\n",
    "    plt.plot([0.5 + i, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=red_grad[i])\n",
    "\n",
    "for i in range(16):\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=blue_grad[i])\n",
    "    plt.plot([0.5, 0.5 + i],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=blue_grad[i])\n",
    "\n",
    "plt.savefig(\"diagrams/pssa_gp.png\", dpi=300)\n"
   ],
   "metadata": {
    "collapsed": false,
    "pycharm": {
     "name": "#%%\n"
    }
   }
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Demonstrate a swap (part 1)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 14,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "grey = \"#696969\"\n",
    "for i in range(16):\n",
    "    c = \"#BF6473\" if i == 5 else grey\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "for i in range(16):\n",
    "    c = \"#BF6473\" if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [15.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "for i in range(8):\n",
    "    c = \"#60A2C4\" if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "plt.savefig(\"diagrams/coa_swap_1.png\", dpi=300)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Demonstrate a swap (part 2)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "grey = \"#696969\"\n",
    "for i in range(16):\n",
    "    c = cmap(5) if i == 5 else grey\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "for i in range(16):\n",
    "    c = cmap(5) if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [15.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "for i in range(8):\n",
    "    c = cmap(0) if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "plt.savefig(\"diagrams/coa_swap_2.png\", dpi=300)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Demonstrate a shift (part 1)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 16,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "grey = \"#696969\"\n",
    "for i in range(16):\n",
    "    c = cmap(0) if i == 5 else grey\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "for i in range(16):\n",
    "    c = cmap(0) if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [15.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "for i in range(8):\n",
    "    c = cmap(5) if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "plt.savefig(\"diagrams/coa_shift_1.png\", dpi=300)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Demonstrate a shift (part 2)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 17,
   "metadata": {
    "collapsed": false,
    "jupyter": {
     "outputs_hidden": false
    },
    "pycharm": {
     "name": "#%%\n"
    }
   },
   "outputs": [
    {
     "data": {
      "text/plain": "<Figure size 432x288 with 1 Axes>",
      "image/png": "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\n"
     },
     "metadata": {
      "needs_background": "light"
     },
     "output_type": "display_data"
    }
   ],
   "source": [
    "plot_grid()\n",
    "grey = \"#696969\"\n",
    "for i in range(16):\n",
    "    if i == 5:\n",
    "        continue\n",
    "    plt.plot([0.5, 15.5],\n",
    "             [15.5 - i, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=grey)\n",
    "\n",
    "for i in range(16):\n",
    "    c = cmap(0) if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [15.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "for i in range(8):\n",
    "    c = cmap(5) if i == 5 else grey\n",
    "    plt.plot([0.5 + i, 0.5 + i],\n",
    "             [0.5, 15.5 - i],\n",
    "             \"-\", lw=5, solid_capstyle='round', c=c)\n",
    "\n",
    "plt.plot([0.5, 5.25],\n",
    "         [10.25, 10.25],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=cmap(5))\n",
    "\n",
    "plt.plot([5.5, 15.5],\n",
    "         [10.5, 10.5],\n",
    "         \"-\", lw=5, solid_capstyle='round', c=cmap(0))\n",
    "\n",
    "plt.savefig(\"diagrams/coa_shift_2.png\", dpi=300)\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 17,
   "outputs": [],
   "source": [],
   "metadata": {
    "collapsed": false,
    "pycharm": {
     "name": "#%%\n"
    }
   }
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.8.5"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 4
}